/*
 * =====================================================================================
 *
 *       Filename:  tcpServer.h
 *
 *    Description:  
 *
 *        Version:  1.0
 *        Created:  07/26/2012 11:24:06 AM
 *       Revision:  none
 *       Compiler:  gcc/g++
 *
 *         Author:  wangtengchao , wangtengchao AT gmail.com
 *   Organization:  
 *
 * =====================================================================================
 */

#ifndef TCPSERVER_H
#define TCPSERVER_H
//#include "inetAddr.h"
#include "timestamp.h"
#include "acceptor.h"
#include "dispatcher.h"
#include "dispatcherThreadPool.h"
#include <string>
#include<boost/noncopyable.hpp>
#include<boost/scoped_ptr.hpp>
namespace inm
{
    namespace net
    {
        //a server should implement NewConnectCallBack,
        class TcpServer : boost::noncopyable
        {
        public:
            TcpServer(const InetAddr& serverAddr,
                      const std::string& name = "",
                      int threadNum = 1);
            ~TcpServer();
            //for set Accept's newConnectCallBack_
            //in TcpServer because must use Reactor pool
            void newConnectCallback(int sockfd,const InetAddr& newClientAddr,const Timestamp& t);
            void run();//deal with set callback etc
            void quit();
            void setDispatcherThreadNum(int num)
            {
                if(!isStarted && num>=1)
                {//can only be changed when server is not starting and num is 1 at least.
                    threadPoolNum_  = num;
                    dispatcherThreadPool_->setThreadNum(num);
                }
            }
            void defaultMesageCallback(const TcpConnectPtr& t, NetBuffer* buf,const Timestamp& time);

            void setMessageCallback(const MessageCallback& cb)
            {
                messageCallback_ = cb;
            }
            void setConnectCallback(const ConnectionCallback& cb)
            {
                connectCallback_ = cb;
            }
            void setWriteCallback(const WriteCompleteCallback& cb)
            {
                writeCompleteCallbcak_ = cb;
            }
        private:

            InetAddr serverAddr_;
            std::string serverName_;
            Dispatcher* mainDispatcher_;
            Demultiplexer* demultiplexer_;//for main Reactor
            DispatcherThreadPool* dispatcherThreadPool_;
            boost::shared_ptr<Acceptor> acceptor_;//for dispatcher's map .so must be shared_ptr
            int threadPoolNum_;
            // callbacks below  are customized by different users of the network lib
            MessageCallback messageCallback_; //must have
            ConnectionCallback connectCallback_;//can be null
            WriteCompleteCallback writeCompleteCallbcak_;//can be null
            bool isStarted;//
            int nextConnId;

         };

    };
};
#endif
